package com.wb.reggie.controller;

import com.wb.reggie.common.R;
import io.minio.MinioClient;
import io.minio.policy.PolicyType;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;

@Slf4j
@RestController
@RequestMapping("/common")
public class FileUploadController {

    private String URL;
    //获取外部定义参数,@Value("${minio.endpoint}"):读取外部文件
    @Value("${minio.endpoint}")
    private String endpoint;

    @Value("${minio.bucketName}")
    private String bucketName;

    @Value("${minio.accessKey}")
    private String accessKey;

    @Value("${minio.secretKey}")
    private String secretKey;

    @Value("${reggie.path}")
    private String basePath;//在yml指定了一个自定义的文件路径
    /**
     * 要求返回自定义响应信息
     * 文件上传一般用PostMapping
     * 以为前后端工程，有个跨域问题，为了测试，在这里解决（spring cloud有网关就不需要这样做了）
     * @return
     */
    @PostMapping("/upload")
    @CrossOrigin("*")   //解决跨域问题，一半写个*即可，代表什么都可以跨域
    public R upload(MultipartFile file){
        //把二进制文件存储到minion中
        try {
            //1，创建minion文件上传客户端(端口，账号，密码，)
            MinioClient minioClient = new MinioClient(endpoint,accessKey,secretKey);

            //2，创建文件的存储桶（文件夹）不需要在minion上手动创建
            boolean isExit = minioClient.bucketExists(bucketName);
            if(!isExit){//没有就创建
                minioClient.makeBucket(bucketName);
                //设置权限
                minioClient.setBucketPolicy(bucketName,"*.*", PolicyType.READ_ONLY);
            }

            //3,设置存储对象（文件）的名称（路径），规则自己定义，例如用实时时间定义文件夹
            SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMdd");
            String filename = file.getOriginalFilename();//上传文件的名称
            String objName = sdf.format(new Date()) + "/" +filename;//最终的名称：通过时间＋图片的名称来拼接的
            log.info("最终文件名：{}",objName);

            //4，把存储对象保存至存储桶中
            //putObject(放到哪个文件夹，哪个对象，文件的二进制输入流，文件类型)
            minioClient.putObject(bucketName,objName,file.getInputStream(),file.getContentType());

            //设置一个访问的地址待会儿用于返回，是图片在minion的绝对路径
            String objUrl = minioClient.getObjectUrl(bucketName,objName);
            log.info("文件上传成功：{}",objUrl);

            URL = objUrl;

            return R.success(objUrl);
            //以前是这样放的
            // file.transferTo();//直接放在当前容器的目录
        }catch (Exception e){
            e.printStackTrace();

            return R.error("上传失败");
        }

    }
}
